package link.ahsj.sqlserver.service.impl;

import cn.hutool.core.io.watch.WatchMonitor;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import link.ahsj.sqlserver.entity.*;
import link.ahsj.sqlserver.exception.BaseBusinessException;
import link.ahsj.sqlserver.mapper.*;
import link.ahsj.sqlserver.service.BusiessService;
import link.ahsj.sqlserver.utils.FileUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.io.File;
import java.io.IOException;
import java.util.List;

@Service
@Slf4j
public class BusiessServiceImpl implements BusiessService {

    //1.药品目录
    @Autowired
    private YpxxlbMapper ypxxlbMapper;
    //2.供应商信息
    @Autowired
    private GysxxlbMapper gysxxlbMapper;
    //3.上传采购订单
    @Autowired
    private SccgddMapper sccgddMapper;
    //4.上传收获单据
    @Autowired
    private ScshdjMapper scshdjMapper;
    //5.上传验收入库单据
    @Autowired
    private ScysrkdjMapper scysrkdjMapper;
    //6.上传退货入库单据
    @Autowired
    private ScthckdjMapper scthckdjMapper;
    //7.上传实时库存数据
    @Autowired
    private KcmxlbMapper kcmxlbMapper;
    //8.上传库存盘点
    @Autowired
    private SckcpdMapper sckcpdMapper;
    //9.1医保读卡
    //@Autowired
    //private YbdkMapper ydbkmapper;
    //9.2销售出库
    @Autowired
    private XsckMapper xsckMapper;
    //9.2销售退货
    @Autowired
    private XsthMapper xsthMapper;




    //10.上传药店药师信息
    private ScydysxxMapper scydysxxMapper;




    @Override
    public void list1(String startTime,String endTime) throws IOException {
        log.info("这是上传药品目录信息");
        FileUtil.checkFile();
        Scypmlxx scypmlxx = new Scypmlxx();
        scypmlxx.setYpxxlb(ypxxlbMapper.getYpxxlbList());

        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YPXX00";
        try {
            FileUtil.createReqFile(reply, flag, scypmlxx, method);
        } catch (BaseBusinessException e) {
            watchMonitor.close();
            throw e;
        } catch (Exception e) {
            log.error(method + "程序内部错误:" + e.getMessage());
            log.error(method + "程序内部错误:" + e.getStackTrace());
            log.error(method + "程序内部错误:" + e.getCause());
            log.error(e.toString());
            watchMonitor.close();
            throw e;
        }
        watchMonitor.close();
        log.info("上传药品目录信息结束");
    }

    @Override
    public void list2(String startTime,String endTime) throws IOException {
        FileUtil.checkFile();
        log.info("这是上传供应商信息");
        Scgysxx scgysxx = new Scgysxx();
        scgysxx.setGysxxlb(gysxxlbMapper.getGysxxlbList());

        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "GYS000";
        try {
            FileUtil.createReqFile(reply, flag, scgysxx, method);
        } catch (BaseBusinessException e) {
            watchMonitor.close();
            throw e;
        } catch (Exception e) {
            log.error(method + "程序内部错误:" + e.getMessage());
            log.error(method + "程序内部错误:" + e.getStackTrace());
            log.error(method + "程序内部错误:" + e.getCause());
            log.error(e.toString());
            watchMonitor.close();
            throw e;
        }
        watchMonitor.close();
        log.info("上传供应商信息结束");
    }

    @Override
    public void list3(String startTime,String endTime) throws IOException,BaseBusinessException {
        //第一次进入方法要删除应答文件
        //加入此定时任务时间到了要开始执行,但是应答文件是上一个程序的(由于reply中参数是错误的,所以上一个程序一直等待),要如何处理--已经处理完毕
        FileUtil.checkFile();
        log.info("这是上传采购订单");

        List<Sccgdd> ddmxlbList = sccgddMapper.getDdmxlbList(startTime,endTime);
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "CGDD00";
        for (Sccgdd sccgdd : ddmxlbList) {
            //创建请求入参文件request.txt
            try {
                FileUtil.createReqFile(reply, flag, sccgdd, method);
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("上传采购订单结束");
    }

    @Override
    public void list4(String startTime,String endTime) throws IOException {
        //第一次进入方法要删除应答文件
        //加入此定时任务时间到了要开始执行,但是应答文件是上一个程序的(由于reply中参数是错误的,所以上一个程序一直等待),要如何处理--已经处理完毕
        FileUtil.checkFile();
        log.info("这是上传收获单据");

        List<Scshdj> scshdjList = scshdjMapper.getScshdjList(startTime,endTime);
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "CGSH00";
        for (Scshdj scshdj : scshdjList) {
            //创建请求入参文件request.txt
            try {
                FileUtil.createReqFile(reply, flag, scshdj, method);
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("上传收获单据结束");
    }

    @Override
    public void list5(String startTime,String endTime) throws IOException {
        //第一次进入方法要删除应答文件
        //加入此定时任务时间到了要开始执行,但是应答文件是上一个程序的(由于reply中参数是错误的,所以上一个程序一直等待),要如何处理--已经处理完毕
        FileUtil.checkFile();
        log.info("这是上传验收入库单据");

        List<Scysrkdj> scysrkdjList = scysrkdjMapper.getScysrkdjList(startTime,endTime);
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YSRK00";
        for (Scysrkdj scysrkdj : scysrkdjList) {
            //创建请求入参文件request.txt
            try {
                FileUtil.createReqFile(reply, flag, scysrkdj, method);
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("上传验收入库单据结束");
    }

    @Override
    public void list6(String startTime,String endTime) throws IOException {
//第一次进入方法要删除应答文件
        //加入此定时任务时间到了要开始执行,但是应答文件是上一个程序的(由于reply中参数是错误的,所以上一个程序一直等待),要如何处理--已经处理完毕
        FileUtil.checkFile();
        log.info("这是上传退货出库单据");

        List<Scthckdj> scthckdjList = scthckdjMapper.getScthckdjList(startTime,endTime);
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YSRK00";
        for (Scthckdj scthckdj : scthckdjList) {
            //创建请求入参文件request.txt
            try {
                FileUtil.createReqFile(reply, flag, scthckdj, method);
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("上传退货出库单据结束");
    }


    @Override
    public void list7(String startTime,String endTime) throws IOException {
        log.info("这是上传实时库存数据");
        FileUtil.checkFile();
        Scsskcsj scsskcsj = new Scsskcsj();
        scsskcsj.setKcmxlb(kcmxlbMapper.getKcmxlbList());

        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YPKCXX";
        try {
            FileUtil.createReqFile(reply, flag, scsskcsj, method);
        } catch (BaseBusinessException e) {
            watchMonitor.close();
            throw e;
        } catch (Exception e) {
            log.error(method + "程序内部错误:" + e.getMessage());
            log.error(method + "程序内部错误:" + e.getStackTrace());
            log.error(method + "程序内部错误:" + e.getCause());
            log.error(e.toString());
            watchMonitor.close();
            throw e;
        }
        watchMonitor.close();
        log.info("上传实时库存数据结束");
    }

    @Override
    public void list8(String startTime,String endTime) throws IOException {
        log.info("这是上传库存盘点");
        FileUtil.checkFile();
        List<Sckcpd> sckcpdList = sckcpdMapper.getSckcpdList();
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YPKCPD";
        for (Sckcpd sckcpd : sckcpdList) {
            //创建请求入参文件request.txt
            try {
                FileUtil.createReqFile(reply, flag, sckcpd, method);
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("上传库存盘点结束");
    }

    @Override
    public void list91(String startTime,String endTime) {

    }


    @Override
    public void list92(String startTime,String endTime) throws IOException {
        log.info("这是销售出库");
        FileUtil.checkFile();
        List<XsckReq> xsckList = xsckMapper.getXsckList();
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YPLS00";
        for (XsckReq xsckReq : xsckList) {
            //创建请求入参文件request.txt
            try {
                ScxsResVo scxResVo = FileUtil.createReqFileFor9(reply, flag, xsckReq, method);
                if ("TRUE".equals(scxResVo.getReply()) && !method.equals(scxResVo.getMethod()) && "TRUE".equals(scxResVo.getSuccess())){
                    scxResVo.setEntity(JSONUtil.toBean((JSONObject) scxResVo.getEntity(),XsckRes.class));
                    xsckMapper.insert((XsckRes)scxResVo.getEntity());
                }
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("销售出库结束");
    }

    @Override
    public void list93(String startTime,String endTime) throws IOException {
        log.info("这是销售退货");
        FileUtil.checkFile();
        List<XsthReq> xsthList = xsthMapper.getXsthList();
        File reply = new File(FileUtil.REPLY_PATH);
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YPLSTH";
        for (XsthReq xsthReq : xsthList) {
            //创建请求入参文件request.txt
            try {
                ScxsResVo scxResVo = FileUtil.createReqFileFor9(reply, flag, xsthReq, method);
                if ("TRUE".equals(scxResVo.getReply()) && !method.equals(scxResVo.getMethod()) && "TRUE".equals(scxResVo.getSuccess())){
                    scxResVo.setEntity(JSONUtil.toBean((JSONObject) scxResVo.getEntity(),XsthRes.class));
                    xsthMapper.insert((XsthRes)scxResVo.getEntity());
                }
            } catch (BaseBusinessException e) {
                watchMonitor.close();
                throw e;
            } catch (Exception e) {
                log.error(method + "程序内部错误:" + e.getMessage());
                log.error(method + "程序内部错误:" + e.getStackTrace());
                log.error(method + "程序内部错误:" + e.getCause());
                log.error(e.toString());
                watchMonitor.close();
                throw e;
            }
        }
        watchMonitor.close();
        log.info("销售退货结束");
    }
    @Override
    public void list10(String startTime,String endTime) throws IOException {
        log.info("这是上传实时库存数据");
        FileUtil.checkFile();
        Scydysxx scydysxx = new Scydysxx();
        scydysxx.setYsmxlb(scydysxxMapper.getYpxxlbList());

        File reply = new File(FileUtil.REPLY_PATH);
        //阻塞程序的开关,true时程序阻塞,监听reply.txt文件是否生成,false表示已经生成监听文件,继续向下执行程序
        final boolean[] flag = {true};
        //监听应答文件是否新增,若新增,则将flag设为false;
        WatchMonitor watchMonitor = FileUtil.monitorFileChange(reply, flag);
        String method = "YDYS00";
        try {
            FileUtil.createReqFile(reply, flag, scydysxx, method);
        } catch (BaseBusinessException e) {
            watchMonitor.close();
            throw e;
        } catch (Exception e) {
            log.error(method + "程序内部错误:" + e.getMessage());
            log.error(method + "程序内部错误:" + e.getStackTrace());
            log.error(method + "程序内部错误:" + e.getCause());
            log.error(e.toString());
            watchMonitor.close();
            throw e;
        }
        watchMonitor.close();
        log.info("上传实时库存数据结束");
    }
}
